package com.qq.多线程.线程同步.案例.送礼物;

import java.util.ArrayList;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class MyRunnable implements Runnable{
    //两个线程接收的是同一个任务对象，所以对他们来说，
    //任务对象里的所有属性都是共享资源，不管是不是静态
    private int a ;//也可以直接在这给赋值，比代码块先执行
    private int count;
    private int count2;
    private final Lock l1 = new ReentrantLock();
    ArrayList<String> arr = new ArrayList<>();
    {//实例代码块，可以初始化实例成员，并且在内部可以使用方法。
        a = 100;
        for(int i = 0 ; i < a ; i++){
            arr.add("小玩偶" + (i+1) + "号");
        }
    }
//    注：不能在构造方法里给a赋值，因为实例代码块比构造方法先执行

    @Override
    public void run() {
//      也可以使用同步代码块或同步方法的this当做锁，因为Runnable对象是两个线程的共享资源
        String name = Thread.currentThread().getName();//可以在抢锁之前取名字，因为线程都运行各自的run方法
        while (true){
            l1.lock();
            try {
                if(arr.size() < 10){
//                    if(name.equals("小红")){
//                        System.out.println(name + "送了" + count + "个礼物");
//                    }else{
//                        System.out.println(name + "送了" + count2 + "个礼物");
//                    }
                    break;
                }
                if(name.equals("小红")){
                    System.out.println(name+"送出了"+arr.remove(arr.size()-1));//不加锁可能同时发同一个礼物
                    ++count;
                }else {
                    System.out.println(name+"送出了"+arr.remove(arr.size()-1));
                    ++count2;
                }

            } finally {
                //一定要在finally里释放lock锁，不然上面的break;结束循环后，
                // l1.unlock();方法无法执行，将造成死锁，其他线程就永远抢不到锁了
                //同步方法和同步代码块会自动释放
                l1.unlock();
            }

        }
       
    }
    //获取两个人送出的礼物数
    public int getCount(){
        return count;
    }
    public int getCount2(){
        return count2;
    }

}
